﻿using System;
using TY.UC.Common.Extension;
using TY.UT.Pay.WxPay.lib;

namespace TY.UT.Pay.WxPay
{
    public class JsApiPayHelper
    {
        /// <summary>
        /// 调用统一下单，获得下单结果(H5支付)
        /// 失败时抛异常WxPayException
        /// </summary>
        /// <returns>统一下单结果</returns>
        public static string GetUnifiedOrderResult(string body, string outTradeNo, float totalFee, string openid)
        {
            WxPayData data = new WxPayData();
            data.SetValue("body", body); //商品简单描述，该字段须严格按照规范传递，具体请见参数规定
            data.SetValue("attach", "test"); //附加数据，在查询API和支付通知中原样返回，该字段主要用于商户携带订单的自定义数据
            data.SetValue("out_trade_no", outTradeNo); //商户系统内部的订单号,32个字符内、可包含字母, 其他说明见商户订单号
            data.SetValue("total_fee", Convert.ToInt32(totalFee * 100)); //订单总金额，单位为分，详见支付金额
            data.SetValue("time_start", DateTime.Now.ToString("yyyyMMddHHmmss")); //订单生成时间，格式为yyyyMMddHHmmss，
            data.SetValue("time_expire", DateTime.Now.AddMinutes("order_timeout".GetIntValue() == 0 ? 10 : "order_timeout".GetIntValue()).ToString("yyyyMMddHHmmss"));
            //订单失效时间，格式为yyyyMMddHHmmss 注意：最短失效时间间隔必须大于5分钟
            data.SetValue("goods_tag", "test"); //商品标记，代金券或立减优惠功能的参数，说明详见代金券或立减优惠
            data.SetValue("trade_type", "JSAPI"); //取值如下：JSAPI--公众号支付、NATIVE--原生扫码支付、APP--app支付，详细说明见参数规定
            data.SetValue("openid", openid); //用户在商户appid下的唯一标识

            WxPayData result = WxPayApi.UnifiedOrder(data, 12); //默认12秒，减少微信请求超时
            if (result.IsSet("appid") && result.IsSet("prepay_id") && result.GetValue("prepay_id").ToString() != "")
            {
                WxPayData jsApiParam = new WxPayData();
                jsApiParam.SetValue("appId", result.GetValue("appid")); //
                jsApiParam.SetValue("timeStamp", WxPayApi.GenerateTimeStamp()); //生成时间戳
                jsApiParam.SetValue("nonceStr", WxPayApi.GenerateNonceStr()); // 生成随机串，随机串包含字母或数字
                jsApiParam.SetValue("package", "prepay_id=" + result.GetValue("prepay_id")); //
                jsApiParam.SetValue("signType", "MD5");
                jsApiParam.SetValue("paySign", jsApiParam.MakeSign());
                jsApiParam.SetValue("total_fee", totalFee); //订单总金额，单位为分，详见支付金额
                jsApiParam.SetValue("out_trade_no", outTradeNo);
                string parameters = jsApiParam.ToJson();

                Log.Debug("JsApiPayHelper-GetUnifiedOrderResult", "Get jsApiParam : " + parameters);
                return parameters;
            }
            Log.Error("JsApiPayHelper-GetUnifiedOrderResult", "UnifiedOrder response error!");
            return null;
        }
        /// <summary>
        /// 调用统一下单，获得下单结果(APP支付)
        /// created by 黄星星 on 2016-12-12
        /// </summary>
        /// <returns>统一下单结果</returns>
        public static object GetAPPUnifiedOrderResult(string body, string outTradeNo, float totalFee)
        {
            WxPayData data = new WxPayData();
            data.SetValue("body", body); //商品简单描述，该字段须严格按照规范传递，具体请见参数规定
            data.SetValue("attach", "test"); //附加数据，在查询API和支付通知中原样返回，该字段主要用于商户携带订单的自定义数据
            data.SetValue("out_trade_no", outTradeNo); //商户系统内部的订单号,32个字符内、可包含字母, 其他说明见商户订单号
            data.SetValue("total_fee", Convert.ToInt32(totalFee * 100)); //订单总金额，单位为分，详见支付金额
            data.SetValue("time_start", DateTime.Now.ToString("yyyyMMddHHmmss")); //订单生成时间，格式为yyyyMMddHHmmss，
            data.SetValue("time_expire", DateTime.Now.AddMinutes("order_timeout".GetIntValue() == 0 ? 10 : "order_timeout".GetIntValue()).ToString("yyyyMMddHHmmss"));
            //订单失效时间，格式为yyyyMMddHHmmss 注意：最短失效时间间隔必须大于5分钟
            data.SetValue("goods_tag", "test"); //商品标记，代金券或立减优惠功能的参数，说明详见代金券或立减优惠
            data.SetValue("trade_type", "APP"); //取值如下：JSAPI--公众号支付、NATIVE--原生扫码支付、APP--app支付，详细说明见参数规定 

            WxPayData result = WxPayApi.APPUnifiedOrder(data, 12); //默认12秒，减少微信请求超时

            Log.Info("JsApiPayHelper-GetAPPUnifiedOrderResult，申请支付返回结果：", result.ToJson());

            if (result.IsSet("appid") && result.IsSet("prepay_id") && result.GetValue("prepay_id").ToString() != "")
            {
                WxPayData jsApiParam = new WxPayData();
                jsApiParam.SetValue("appid", WxPayConfig.SHAppId); //微信开放平台审核通过的应用APPID
                jsApiParam.SetValue("partnerid", WxPayConfig.SHMchid); //微信支付分配的商户号
                jsApiParam.SetValue("prepayid", result.GetValue("prepay_id")); //微信返回的支付交易会话ID
                jsApiParam.SetValue("package", "Sign=WXPay"); //暂填写固定值Sign=WXPay 
                jsApiParam.SetValue("noncestr", WxPayApi.GenerateNonceStr()); // 生成随机串，随机串包含字母或数字
                jsApiParam.SetValue("timestamp", WxPayApi.GenerateTimeStamp()); //生成时间戳 
                //jsApiParam.SetValue("signType", "MD5");
                jsApiParam.SetValue("sign", jsApiParam.MakeSHSign());
                var obj =
                    new WxSignResult
                    {
                        appid = WxPayConfig.SHAppId,
                        partnerid = WxPayConfig.SHMchid,
                        prepayid = result.GetValue("prepay_id"),
                        package = "Sign=WXPay",
                        noncestr = jsApiParam.GetValue("noncestr"),
                        timestamp = jsApiParam.GetValue("timestamp"),
                        sign = jsApiParam.MakeSHSign()
                    };
                //string parameters = jsApiParam.ToJson(); 
                Log.Debug("JsApiPayHelper-GetAPPUnifiedOrderResult", "Get jsApiParam : " + jsApiParam.ToJson());
                return obj;
            }

            Log.Error("GetAPPUnifiedOrderResult-GetAPPUnifiedOrderResult", "UnifiedOrder response error!");
            return null;
        }

        /// <summary>
        /// 调用统一下单，获得下单结果(小程序下单，因为小程序的appid与公众号的appid不一样，商户信息可以公用)
        /// 失败时抛异常WxPayException
        /// </summary>
        /// <returns>统一下单结果</returns>
        public static string GetUnifiedOrderResultForLittlePro(string body, string outTradeNo, float totalFee, string openid)
        {
            WxPayData data = new WxPayData();
            data.SetValue("body", body); //商品简单描述，该字段须严格按照规范传递，具体请见参数规定
            data.SetValue("attach", "test"); //附加数据，在查询API和支付通知中原样返回，该字段主要用于商户携带订单的自定义数据
            data.SetValue("out_trade_no", outTradeNo); //商户系统内部的订单号,32个字符内、可包含字母, 其他说明见商户订单号
            data.SetValue("total_fee", Convert.ToInt32(totalFee * 100)); //订单总金额，单位为分，详见支付金额
            data.SetValue("time_start", DateTime.Now.ToString("yyyyMMddHHmmss")); //订单生成时间，格式为yyyyMMddHHmmss，
            data.SetValue("time_expire", DateTime.Now.AddMinutes("order_timeout".GetIntValue() == 0 ? 10 : "order_timeout".GetIntValue()).ToString("yyyyMMddHHmmss"));
            //订单失效时间，格式为yyyyMMddHHmmss 注意：最短失效时间间隔必须大于5分钟
            data.SetValue("goods_tag", "test"); //商品标记，代金券或立减优惠功能的参数，说明详见代金券或立减优惠
            data.SetValue("trade_type", "JSAPI"); //取值如下：JSAPI--公众号支付、NATIVE--原生扫码支付、APP--app支付，详细说明见参数规定
            data.SetValue("openid", openid); //用户在商户appid下的唯一标识

            WxPayData result = WxPayApi.UnifiedOrderForLittlePro(data, 12); //默认12秒，减少微信请求超时
            if (result.IsSet("appid") && result.IsSet("prepay_id") && result.GetValue("prepay_id").ToString() != "")
            {
                WxPayData jsApiParam = new WxPayData();
                jsApiParam.SetValue("appId", result.GetValue("appid")); //
                jsApiParam.SetValue("timeStamp", WxPayApi.GenerateTimeStamp()); //生成时间戳
                jsApiParam.SetValue("nonceStr", WxPayApi.GenerateNonceStr()); // 生成随机串，随机串包含字母或数字
                jsApiParam.SetValue("package", "prepay_id=" + result.GetValue("prepay_id")); //
                jsApiParam.SetValue("signType", "MD5");
                jsApiParam.SetValue("paySign", jsApiParam.MakeSign());
                jsApiParam.SetValue("total_fee", totalFee); //订单总金额，单位为分，详见支付金额
                jsApiParam.SetValue("out_trade_no", outTradeNo);
                string parameters = jsApiParam.ToJson();

                Log.Debug("JsApiPayHelper-GetUnifiedOrderResult", "Get jsApiParam : " + parameters);
                return parameters;
            }
            Log.Error("JsApiPayHelper-GetUnifiedOrderResult", "UnifiedOrder response error!");
            return null;
        }



        /// <summary>
        /// 调用统一下单，获得下单结果(PC扫码支付)
        /// 失败时抛异常WxPayException
        /// </summary>
        /// <returns>统一下单结果</returns>
        public static string GetPCUnifiedOrderResult(string body, string outTradeNo, decimal totalFee, string product_id)
        {

            WxPayData data = new WxPayData();
            data.SetValue("body", body); //商品简单描述，该字段须严格按照规范传递，具体请见参数规定
            data.SetValue("attach", "test"); //附加数据，在查询API和支付通知中原样返回，该字段主要用于商户携带订单的自定义数据
            data.SetValue("out_trade_no", outTradeNo); //商户系统内部的订单号,32个字符内、可包含字母, 其他说明见商户订单号
            data.SetValue("total_fee", Convert.ToInt32(totalFee * 100)); //订单总金额，单位为分，详见支付金额
            data.SetValue("time_start", DateTime.Now.ToString("yyyyMMddHHmmss")); //订单生成时间，格式为yyyyMMddHHmmss，
            data.SetValue("time_expire", DateTime.Now.AddMinutes("order_timeout".GetIntValue() == 0 ? 10 : "order_timeout".GetIntValue()).ToString("yyyyMMddHHmmss"));
            //订单失效时间，格式为yyyyMMddHHmmss 注意：最短失效时间间隔必须大于5分钟
            data.SetValue("goods_tag", "test"); //商品标记，代金券或立减优惠功能的参数，说明详见代金券或立减优惠
            data.SetValue("trade_type", "NATIVE"); //取值如下：JSAPI--公众号支付、NATIVE--原生扫码支付、APP--app支付，详细说明见参数规定
            data.SetValue("product_id", product_id); //商品ID     trade_type=NATIVE时（即扫码支付），此参数必传。此参数为二维码中包含的商品ID，商户自行定义。

            WxPayData result = WxPayApi.UnifiedOrder(data, 12); //默认12秒，减少微信请求超时
            if (result.IsSet("code_url"))
            {
                //WxPayData jsApiParam = new WxPayData();
                //jsApiParam.SetValue("appId", result.GetValue("appid")); //
                //jsApiParam.SetValue("timeStamp", WxPayApi.GenerateTimeStamp()); //生成时间戳
                //jsApiParam.SetValue("nonceStr", WxPayApi.GenerateNonceStr()); // 生成随机串，随机串包含字母或数字
                //jsApiParam.SetValue("package", "prepay_id=" + result.GetValue("prepay_id")); //
                //jsApiParam.SetValue("signType", "MD5");
                //jsApiParam.SetValue("paySign", jsApiParam.MakeSign());
                //jsApiParam.SetValue("total_fee", totalFee); //订单总金额，单位为分，详见支付金额
                //jsApiParam.SetValue("out_trade_no", outTradeNo);
                //jsApiParam.SetValue("code_url", result.GetValue("code_url"));
                //string parameters = jsApiParam.ToJson();

                Log.Debug("JsApiPayHelper-GetPCUnifiedOrderResult", "Get code_url : " + result.GetValue("code_url"));
                return result.GetValue("code_url") + "";
            }
            Log.Error("JsApiPayHelper-GetPCUnifiedOrderResult", "UnifiedOrder response error!");
            return null;
        }
    }
    /// <summary>
    /// 小程序支付签名模型
    /// </summary>
    public class PrePayModel
    {
        public string appId { get; set; }
        public string out_trade_no { get; set; }
        /// <summary>
        /// prepay_id=wx1809071567923001fe28b3c62032467763
        /// </summary>
        public string package { get; set; }
        public string paySign { get; set; } 
    }
}
